package com.xhwl.centiotdata.pushtrigger.pedestrian;

import cn.hutool.extra.servlet.ServletUtil;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import com.xhwl.centiotdata.handler.pedestrian.impl.PedestrianIntegrationHuaWeiIoTDAHandler;
import com.xhwl.centiotdata.handler.pedestrian.impl.PedestrianIntegrationKeyTopLocalHandler;
import com.xhwl.centiotdata.pojo.dto.huawei.PedestrianRecordHuaWeiIoTDADTO;
import com.xhwl.centiotdata.pojo.dto.keytoplocal.AccessInfoKeyTopLocalDTO;
import com.xhwl.centiotdata.pojo.dto.pedestrian.PedestrianIntegrationConfigDTO;
import com.xhwl.centiotdata.pojo.enums.pedestrian.PedestrianMethodEnum;
import com.xhwl.centiotdata.service.integrateconfig.PedestrianIntegrationConfig;
import com.xhwl.common.dto.cent.device.iot.DeviceServiceBody;
import com.xhwl.common.dto.cent.device.iot.IotDeviceJson;
import com.xhwl.common.enums.ProductEnum;
import com.xhwl.common.exception.BusinessException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;
import java.net.InetAddress;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.UnknownHostException;
import java.util.List;

/**
 * @Author： lianghz
 * @Description：
 * @Date 2021/12/03/ 11:58
 */
@Slf4j
@RestController
public class PedestrianCallBackController {

    @Autowired
    private PedestrianIntegrationHuaWeiIoTDAHandler handler;

    @Autowired
    private PedestrianIntegrationKeyTopLocalHandler keyTopLocalHandler;

    @Autowired
    private PedestrianIntegrationConfig integrationConfig;

    @PostMapping("/pedestrian/huawei-iotda/access-information/{projectId}")
    public void pushAccessInformation(@RequestBody String data, @PathVariable Integer projectId) {
        log.info("pushAccessInformation" + data);
        IotDeviceJson<DeviceServiceBody<PedestrianRecordHuaWeiIoTDADTO>> json = null;
        try {
            json = JSON.parseObject(data, new TypeReference<IotDeviceJson<DeviceServiceBody<PedestrianRecordHuaWeiIoTDADTO>>>() {
            });
        } catch (Exception e) {
            e.printStackTrace();
            log.error("pushAccessInformation format JSON : ", data);
        }
        if (json != null) {
            handler.pushRecord(json, projectId);
        }
    }


    /**
     * 科拓人行2.0-本地对接-出入报表回调接口
     * 中海寰宇、汇德理、橡树园这三个项目人行都是对接科拓本地，且共用一个后台，回调接口的url也不能改，只能用ip区分是哪个项目发来的出入报表数据
     */
    @PostMapping("/upload/uploadAccessInfo")
    public void uploadAccessInfo(@RequestBody JSONObject json, HttpServletRequest request) {
        log.info("收到科拓推送的出入报表： {}", JSONUtil.toJsonStr(json));
        // 获取消息来源ip
        String ip = ServletUtil.getClientIP(request);
        log.info("ip: {}", ip);

        AccessInfoKeyTopLocalDTO accessInfoKeyTopLocalDTO = null;
        try {
            accessInfoKeyTopLocalDTO = JSONUtil.toBean(json, AccessInfoKeyTopLocalDTO.class);
        } catch (Exception e) {
            e.printStackTrace();
            log.error("pushAccessInformation format JSON : ", json);
        }

        List<PedestrianIntegrationConfigDTO> configDTOList = integrationConfig.getIntegrationConfig(null).get(PedestrianMethodEnum.RECORD.getId());
        if (CollectionUtils.isEmpty(configDTOList)) {
            throw new BusinessException("未找到出入记录配置");
        }

        // 找出与消息来源IP相同的集成配置
        for(PedestrianIntegrationConfigDTO config : configDTOList) {
            if(config.getProductId().equals(ProductEnum.KEYTOP_LOCAL.getId())) {
                String ipAndPort = config.getIpAndPort();
                URL url;
                try {
                    url = new URL(ipAndPort);
                } catch (MalformedURLException e) {
                    log.error("ipAndPort格式错误: {}", ipAndPort);
                    throw new RuntimeException(e);
                }
                try {
                    InetAddress msgIp = InetAddress.getByName(ip);
                    InetAddress configIp = InetAddress.getByName(url.getHost());
                    // 将消息来源ip与集成配置中的ip比较是否相同
                    if(msgIp.equals(configIp)) {
                        keyTopLocalHandler.pushRecord(accessInfoKeyTopLocalDTO, config);
                    }
                } catch (UnknownHostException e) {
                    log.error("ip转换异常： userIp:{}, configIp: {}", ip, url.getHost());
                    throw new RuntimeException(e);
                }
            }
        }
    }

}
